﻿//Copyright (C) 2009  Jaco (ScionBot.com)

//This program is free software: you can redistribute it and/or modify
//it under the terms of the GNU General Public License as published by
//the Free Software Foundation, either version 3 of the License, or
//(at your option) any later version.

//This program is distributed in the hope that it will be useful,
//but WITHOUT ANY WARRANTY; without even the implied warranty of
//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
//GNU General Public License for more details.

//You should have received a copy of the GNU General Public License
//along with this program.  If not, see <http://www.gnu.org/licenses/>.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Scion.Library;
using Scion.Library.Underlying;
using System.Drawing;
using Scion.Library.Antiban;
using Scion.Library.Advanced;

namespace Scion.Library.RS.UI
{
    /// <summary>
    /// Contains equipment functions.
    /// </summary>
    public class Equipment : Determine
    {
        Superior super;

        /// <summary>
        /// Contains equipment functions.
        /// <param name="s">The instance of the bot.</param>
        /// </summary>
        public Equipment(Superior s)
        {
            super = s;
        }

        /// <summary>
        /// Removes a single item from the equipment tab.
        /// </summary>
        /// <param name="item">The item to remove.</param>
        /// <returns>Return true the function succeeded.</returns>
        public bool Remove(EquipmentItem item)
        {
            super.Tab.SwitchTab(5);
            super.Sleep(new SleepRandom(400, 500));
            if (ContainsItem(item))
            {
                super.Mouse.MoveClick(DeterminePosition(item), true);
                return true;
            }
            return false;
        }

        /// <summary>
        /// Finds an item in the equipment tab.
        /// </summary>
        /// <param name="topText">The toptext of the item.</param>
        /// <returns>Returns the location of the found item.</returns>
        public EquipmentItem Find(string topText)
        {
            super.Tab.SwitchTab(5);
            foreach (EquipmentItem item in Enum.GetValues(typeof(EquipmentItem)))
            {
                if (ContainsItem(item))
                {
                    super.Mouse.MoveMouse(DeterminePosition(item));
                    super.Sleep(new SleepRandom(50, 100));
                    if (super.TopText.FindText(TopText.Common, topText, TopText.Tolerance))
                        return item;
                }
            }
            return EquipmentItem.NotFound;
        }

        /// <summary>
        /// Removes all the items in the equipment tab.
        /// </summary>
        /// <returns>Return true the function succeeded.</returns>
        public bool RemoveAll()
        {
            super.Tab.SwitchTab(5);
            foreach (EquipmentItem item in Enum.GetValues(typeof(EquipmentItem)))
            {
                if (ContainsItem(item))
                {
                    super.Mouse.MoveClick(DeterminePosition(item), true);
                    super.Sleep(new SleepRandom(400, 500));
                }
            }
            return true;
        }

        /// <summary>
        /// Removes all the items besides the specified ones.
        /// </summary>
        /// <param name="items">The items to skip.</param>
        /// <returns>Return true the function succeeded.</returns>
        public bool RemoveAllBut(EquipmentItem[] items)
        {
            super.Tab.SwitchTab(5);
            foreach (EquipmentItem item in Enum.GetValues(typeof(EquipmentItem)))
            {
                foreach (EquipmentItem skip in items)
                    if (skip == item)
                        goto Next;
                Remove(item);
                super.Sleep(new SleepRandom(300, 400));
            Next: ;
            }
            return true;
        }

        /// <summary>
        /// Figures out if the specified equipment box contains an item.
        /// </summary>
        /// <param name="item">The item to look at.</param>
        /// <returns>Returns true if there is an item.</returns>
        public bool ContainsItem(EquipmentItem item)
        {
            Point pointer = DetermineStartPoint(item);
            Rectangle rect = new Rectangle(pointer.X, pointer.Y, pointer.X + 27, pointer.Y + 27);
            return Decide(super.FindColour(new Rectangle(rect.X, rect.Y, rect.Width, rect.Height), Color.FromArgb(0, 0, 1), 2));
        }

        /// <summary>
        /// Figures out if specified equipment box contains the item with the toptext.
        /// </summary>
        /// <param name="item">The item to look at.</param>
        /// <param name="topText">The top text of the item.</param>
        /// <returns>Returns true if there is an item with the specified top text.</returns>
        public bool ContainsItem(EquipmentItem item, string topText)
        {
            super.Tab.SwitchTab(5);
            if (ContainsItem(item))
            {
                super.Mouse.MoveMouse(DeterminePosition(item));
                super.Sleep(new SleepRandom(50, 100));
                if (super.TopText.FindText(TopText.Common, topText, TopText.Tolerance))
                    return true;
            }
            return false;
        }

        private Point DetermineStartPoint(EquipmentItem item)
        {
            switch (item)
            {
                case EquipmentItem.Arrows:
                    return new Point(670, 252);
                case EquipmentItem.Body:
                    return new Point(629, 291);
                case EquipmentItem.Boots:
                    return new Point(629, 371);
                case EquipmentItem.Cape:
                    return new Point(588, 252);
                case EquipmentItem.Gloves:
                    return new Point(573, 371);
                case EquipmentItem.Helmet:
                    return new Point(629, 213);
                case EquipmentItem.Legs:
                    return new Point(629, 331);
                case EquipmentItem.Necklace:
                    return new Point(629, 252);
                case EquipmentItem.Ring:
                    return new Point(685, 371);
                case EquipmentItem.Shield:
                    return new Point(685, 291);
                case EquipmentItem.Sword:
                    return new Point(573, 291);
            }
            return new Point(-1,-1);
        }

        private Point DeterminePosition(EquipmentItem item)
        {
            Size box = new Size(27, 27);
            switch (item)
            {
                case EquipmentItem.Arrows:
                    return new SizeRandom(box, new Point(670, 252)).random;
                case EquipmentItem.Body:
                    return new SizeRandom(box, new Point(629, 291)).random;
                case EquipmentItem.Boots:
                    return new SizeRandom(box, new Point(629, 371)).random;
                case EquipmentItem.Cape:
                    return new SizeRandom(box, new Point(588, 252)).random;
                case EquipmentItem.Gloves:
                    return new SizeRandom(box, new Point(573, 371)).random;
                case EquipmentItem.Helmet:
                    return new SizeRandom(box, new Point(629, 213)).random;
                case EquipmentItem.Legs:
                    return new SizeRandom(box, new Point(629, 331)).random;
                case EquipmentItem.Necklace:
                    return new SizeRandom(box, new Point(629, 252)).random;
                case EquipmentItem.Ring:
                    return new SizeRandom(box, new Point(685, 371)).random;
                case EquipmentItem.Shield:
                    return new SizeRandom(box, new Point(685, 291)).random;
                case EquipmentItem.Sword:
                    return new SizeRandom(box, new Point(573, 291)).random;
            }
            return new Point(-1, -1);
        }
    }

    /// <summary>
    /// Which item to look at.
    /// </summary>
    public enum EquipmentItem
    {
        Helmet = 1,
        Necklace = 2,
        Body = 3,
        Legs = 4,
        Sword = 5,
        Shield = 6,
        Boots = 7,
        Gloves = 8,
        Ring = 9,
        Arrows = 10,
        Cape = 11,
        NotFound = 12,
    }
}
